package com.mingqijia.gassafety.webserver.service.workorder.impl;

import cn.hutool.core.date.BetweenFormatter;
import cn.hutool.core.date.DateUtil;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.gap.basic.exception.BizException;
import com.mingqijia.gassafety.db.entity.FieldTemplate;
import com.mingqijia.gassafety.db.entity.ServiceComboOrder;
import com.mingqijia.gassafety.db.entity.SmartKitchenLog;
import com.mingqijia.gassafety.db.entity.WorkOrderHistory;
import com.mingqijia.gassafety.db.entity.vo.UserServiceComboVO;
import com.mingqijia.gassafety.db.entity.vo.WorkOrderAndSmartKitVO;
import com.mingqijia.gassafety.db.mapper.ServiceComboOrderMapper;
import com.mingqijia.gassafety.shared.constant.*;
import com.mingqijia.gassafety.shared.request.HuiShengCreateOrderReq;
import com.mingqijia.gassafety.shared.request.HuiShengOrderAddRequest;
import com.mingqijia.gassafety.shared.response.HuiShengAddOrderResponse;
import com.mingqijia.gassafety.shared.response.HuiShengBaseResponse;
import com.mingqijia.gassafety.shared.service.impl.HuiShengServiceImpl;
import com.mingqijia.gassafety.shared.user.UserBackend;
import com.mingqijia.gassafety.shared.utils.ApplicationUtils;
import com.mingqijia.gassafety.shared.utils.commonUtils.DateUtils;
import com.mingqijia.gassafety.shared.utils.commonUtils.SnowflakeUtil;
import com.mingqijia.gassafety.webserver.feign.ConsoleSkFeignClient;
import com.mingqijia.gassafety.webserver.request.BrowserNotifyReason;
import com.mingqijia.gassafety.webserver.request.console.sk.ConsoleSkRecordsRequest;
import com.mingqijia.gassafety.webserver.request.console.sk.ConsoleSkUpdateRequest;
import com.mingqijia.gassafety.webserver.request.workorder.mbp.MbpOrderCreateRequest;
import com.mingqijia.gassafety.webserver.response.ConsoleSkNotifyAlarmResponse;
import com.mingqijia.gassafety.webserver.response.sk.ConsoleSkRecordsList;
import com.mingqijia.gassafety.webserver.response.sk.ConsoleSkRecordsResponse;
import com.mingqijia.gassafety.webserver.response.sk.ConsoleSkUpdateResponse;
import com.mingqijia.gassafety.webserver.service.FieldTemplateService;
import com.mingqijia.gassafety.webserver.service.ServiceComboDetailService;
import com.mingqijia.gassafety.webserver.service.SmartKitchenLogService;
import com.mingqijia.gassafety.webserver.service.workorder.SkWorkOrderService;
import com.mingqijia.gassafety.webserver.service.workorder.WorkOrderHistoryService;
import com.mingqijia.gassafety.webserver.service.workorder.mbp.MbpWorkOrderService;
import com.mingqijia.gassafety.webserver.utils.ApplicationContextUtils;
import com.mingqijia.gassafety.webserver.webSocket.WebSocketProcess;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.ObjectUtils;
import org.springframework.util.StringUtils;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;

/**
 * @author: duanhongxiang
 * @Desc:
 * @create: 2024-09-05 14:32
 **/
@Service
@Slf4j
public class SkWorkOrderServiceImpl implements SkWorkOrderService {
    private final static String split_m = ":";

    @Autowired
    WorkOrderHistoryService workOrderHistoryService;

    @Autowired
    ServiceComboOrderMapper serviceComboOrderMapper;

    @Autowired
    SmartKitchenLogService kitchenLogService;

    @Autowired
    ConsoleSkFeignClient consoleSkFeignClient;

    @Autowired
    WebSocketProcess webSocketProcess;

    @Autowired
    FieldTemplateService fieldTemplateService;

    @Autowired
    ServiceComboDetailService serviceComboDetailService;

    @Autowired
    HuiShengServiceImpl huiShengService;

    @Autowired
    MbpWorkOrderService mbpWorkOrderService;

    @Override
    public void autoCreateOrderByMsg(String spId,String mess) {
        try {
            UserServiceComboVO userServiceComboVO = JSONObject.parseObject(mess, UserServiceComboVO.class);
            String skNotifyAlarmInfo = JSONObject.toJSONString(userServiceComboVO.getSkNotifyAlarmInfo());
            ConsoleSkNotifyAlarmResponse alarmResponse = JSONObject.parseObject(skNotifyAlarmInfo, ConsoleSkNotifyAlarmResponse.class);

            ConsoleSkRecordsRequest consoleSkRecordsRequest = new ConsoleSkRecordsRequest();
            consoleSkRecordsRequest.setId(alarmResponse.getId());
            consoleSkRecordsRequest.setDeviceId(alarmResponse.getDeviceId());
            consoleSkRecordsRequest.setPage(1);
            consoleSkRecordsRequest.setPageSize(1);
            consoleSkRecordsRequest.setDealStatus("0");
            consoleSkRecordsRequest.setSpId(alarmResponse.getSpId());
            log.info("alarmSOSRecords-request:{}", JSONObject.toJSONString(consoleSkRecordsRequest));
            ConsoleSkRecordsResponse skResp = consoleSkFeignClient.alarmSOSRecords(consoleSkRecordsRequest);
            log.info("alarmSOSRecords-response:{}", JSONObject.toJSONString(skResp));

            if (!ObjectUtils.isEmpty(skResp) && 0 == skResp.getCode() && null != skResp.getData() && null != skResp.getData().getList() &&
                    !skResp.getData().getList().isEmpty()) {
                ConsoleSkRecordsList skData = skResp.getData().getList().get(0);
                String userRemark = getRemark(skData);

                QueryWrapper<FieldTemplate> templateQueryWrapper = new QueryWrapper<>();
                templateQueryWrapper.lambda().eq(FieldTemplate::getSpId, spId)
                        .eq(FieldTemplate::getTemplateType, 1)
                        .eq(FieldTemplate::getIsDeleted, 0);
                FieldTemplate fieldTemplate = fieldTemplateService.getOne(templateQueryWrapper);
                int skWorkSystemType = fieldTemplate.getSkWorkSystemType();
                Long workOrderId = 0L;
                MbpOrderCreateRequest req = new MbpOrderCreateRequest();
                BeanUtils.copyProperties(skData,req);
                String appealResult = "工单处理中";
                if (skWorkSystemType == 3) {
                    appealResult = "师傅帮个忙工单处理中";
                    req.setAddress(skData.getServiceAddress());
                    req.setPhone(skData.getPhone() + (StringUtils.isEmpty(skData.getBackupPhone()) ? "" : ";" + skData.getBackupPhone()));
                    workOrderId = createHuiShengWorkOrder(userServiceComboVO, req, spId, 1, skData);
                }
                if (null != workOrderId && workOrderId > 0) {
                    WorkOrderHistory workOrder = workOrderHistoryService.getById(workOrderId);
                    ConsoleSkUpdateRequest skUpdateRequest = new ConsoleSkUpdateRequest();
                    skUpdateRequest.setId(alarmResponse.getId());
                    skUpdateRequest.setDealStatus(1);
                    skUpdateRequest.setContact(skData.getServiceContact());
                    skUpdateRequest.setContactAddress(skData.getContactAddress());
                    skUpdateRequest.setContactPhone(alarmResponse.getPhone());
                    skUpdateRequest.setResult(appealResult);
                    skUpdateRequest.setWorkOrderNo(workOrder.getOrderNo());
                    skUpdateRequest.setSubsCode(skData.getSubsCode());
                    skUpdateRequest.setJvOrgCode(skData.getJvOrgCode());
                    log.info("alarmSOSUpdate-request:{}", JSONObject.toJSONString(skUpdateRequest));
                    ConsoleSkUpdateResponse consoleSkUpdateResponse = consoleSkFeignClient.alarmSOSUpdate(skUpdateRequest);
                    log.info("alarmSOSUpdate-consoleSkUpdateResponse:{}", JSONObject.toJSONString(consoleSkUpdateResponse));

                    createAppealLog(workOrderId, appealResult, userRemark, skData, "系统用户", "system");

                    alarmResponse.setNotifyReason(BrowserNotifyReason.SkOrderAutoGen);
                    alarmResponse.setNotifyName("自动转单");
                    alarmResponse.setNotifyTime(DateUtils.format(new Date(), "yyyy-MM-dd HH:mm:ss"));
                    alarmResponse.setIsPop(true);
                    alarmResponse.setIsSystem(true);
                    alarmResponse.setMemberId(alarmResponse.getUserId());
                    webSocketProcess.redisTopicSendMsg(alarmResponse.getSpId(), JSONObject.toJSONString(alarmResponse));
                }
            }
        }catch (Exception e){
            log.error("autoCreateOrderByMsg Error", e);
        }
    }

    @Override
    public Long manualCreateOrder(MbpOrderCreateRequest params,String spId) {
        String code = String.valueOf(params.getDeviceType());
        int userId = params.getMemberId();
        UserServiceComboVO userServiceComboVO = serviceComboDetailService.getUserServiceCombo(code, userId, spId);

        ConsoleSkRecordsRequest consoleSkRecordsRequest = new ConsoleSkRecordsRequest();
        consoleSkRecordsRequest.setId(params.getId());
        consoleSkRecordsRequest.setDeviceId(params.getImei());
        consoleSkRecordsRequest.setPage(1);
        consoleSkRecordsRequest.setPageSize(1);
        consoleSkRecordsRequest.setDealStatus("0");
        consoleSkRecordsRequest.setSpId(spId);
        log.info("alarmSOSRecords-request:{}",JSONObject.toJSONString(consoleSkRecordsRequest));
        ConsoleSkRecordsResponse skResp = consoleSkFeignClient.alarmSOSRecords(consoleSkRecordsRequest);
        log.info("alarmSOSRecords-response:{}",JSONObject.toJSONString(skResp));

        if (!ObjectUtils.isEmpty(skResp) && 0 == skResp.getCode() && null != skResp.getData() && null != skResp.getData().getList() &&
                !skResp.getData().getList().isEmpty()) {
            ConsoleSkRecordsList skData = skResp.getData().getList().get(0);

            Long shengWorkOrder = createHuiShengWorkOrder(userServiceComboVO, params, spId, 0, skData);
            //webSocket 给前端的参数
            ConsoleSkNotifyAlarmResponse response = new ConsoleSkNotifyAlarmResponse();
            BeanUtils.copyProperties(skData, response);
            response.setNotifyName(ConsoleSkAlarmTypeEnum.getTypeByCode(skData.getAlarmType()));
            response.setNotifyTime(skData.getAlarmTime());
            response.setImei(skData.getDeviceId());
            response.setInstallationPosition(skData.getRoomName());
            response.setEquipmentTypeName(ConsoleSkDeviceTypeEnum.getTypeByCode(skData.getDeviceType()));
            response.setPhone(skData.getPhone());
            response.setNotifyName("手动转单");
            response.setNotifyReason(BrowserNotifyReason.SkOrderAutoGen);
            response.setIsPop(true);
            response.setIsSystem(true);
            response.setMemberId(response.getUserId());
            if (!StringUtils.isEmpty(params.getCustName())) {
                response.setCustName(params.getCustName());
            }
            response.setNotifyTime(DateUtils.format(new Date(), "yyyy-MM-dd HH:mm:ss"));
            webSocketProcess.redisTopicSendMsg(skData.getSpId(), JSONObject.toJSONString(response));
            return shengWorkOrder;
        } else{
            throw new BizException("未找到设备的报警信息");
        }
    }

    /**
     * 创建师傅帮个忙工单
     * @param userServiceComboVO
     * @param params
     * @param spId
     * @param isAuto
     * @return
     */
    public Long createHuiShengWorkOrder(UserServiceComboVO userServiceComboVO,MbpOrderCreateRequest params,String spId,Integer isAuto, ConsoleSkRecordsList skData){
        String buyerName = "";
        String mobile = "";
        if (!ObjectUtils.isEmpty(userServiceComboVO)) {
            buyerName = userServiceComboVO.getUserName();
            mobile = userServiceComboVO.getPhone();
        }
        ConsoleSkRecordsRequest consoleSkRecordsRequest = new ConsoleSkRecordsRequest();
        consoleSkRecordsRequest.setId(params.getId());
        consoleSkRecordsRequest.setDeviceId(params.getImei());
        consoleSkRecordsRequest.setPage(1);
        consoleSkRecordsRequest.setPageSize(1);
        consoleSkRecordsRequest.setDealStatus("0");
        consoleSkRecordsRequest.setSpId(spId);
        log.info("alarmSOSRecords-request:{}",JSONObject.toJSONString(consoleSkRecordsRequest));
        ConsoleSkRecordsResponse skResp = consoleSkFeignClient.alarmSOSRecords(consoleSkRecordsRequest);
        log.info("alarmSOSRecords-response:{}",JSONObject.toJSONString(skResp));

//        if (!ObjectUtils.isEmpty(skResp) && 0 == skResp.getCode() && null != skResp.getData() && null != skResp.getData().getList() &&
//                !skResp.getData().getList().isEmpty()) {
          if (skData!= null) {
            //ConsoleSkRecordsList skData = skResp.getData().getList().get(0);
            String userRemark = getRemark(skData);
            if (skData!= null && StringUtils.isEmpty(mobile)) {
                mobile = skData.getPhone();
                buyerName = skData.getServiceContact();
            }
            if (StringUtils.isEmpty(mobile)) {
                throw new BizException("未找到用户手机信息");
            }

            String token = huiShengService.login(mobile);
            HuiShengCreateOrderReq request = new HuiShengCreateOrderReq();
            request.setToken(token);
            request.setBuyer_name(buyerName);
            request.setMobile(mobile);
            request.setAddress(params.getAddress());
            //TODO 周淼
            request.setServ_id("46");
            request.setItem_id("172");
            request.setNeed_time_old(params.getBookDate());
            request.setRemark(userRemark);
            request.setLat(skData.getLat());
            request.setLng(skData.getLon());
            String orderNo = huiShengService.createOrder(request);
            UserBackend workingUser = null;
            try{
                workingUser = ApplicationUtils.getWorkingUser();
            }catch (Exception e){
                log.error("workingUser:",e);
            }
            String operateBy = "系统";
            if (null != workingUser) {
                operateBy = StringUtils.isEmpty(workingUser.getName()) ? "" : workingUser.getName();
                operateBy += "(" + (StringUtils.isEmpty(workingUser.getUsername()) ? "" : workingUser.getUsername()) + ")";
            }
            long workOrderId = createWorkOrder(orderNo, skData,operateBy);
            createServiceComboOrder(orderNo, userServiceComboVO, skData, isAuto);
            return workOrderId;
        }else{
            throw new BizException("未找到设备的报警信息");
        }
    }

    /**
     * 创建诉求
     * @param workOrderId
     * @param appealResult
     * @param remark
     * @param skData
     */
    private void createAppealLog(long workOrderId,
                                 String appealResult,
                                 String remark,
                                 ConsoleSkRecordsList skData,
                                 String userName,
                                 String userAccount) {
        SmartKitchenLog appealLog = new SmartKitchenLog();
        appealLog.setWorkorderId(workOrderId);
        appealLog.setRecordId(skData.getId());
        appealLog.setAppealStatus(Constants.APPEAL_STATUS_1);
        appealLog.setSpId(skData.getSpId());
        appealLog.setUserName(userName);
        appealLog.setUserAccount(userAccount);
        appealLog.setAppealResult(appealResult);
        appealLog.setAppealType(0);
        int bizType = SkConst.SK_DEVICE_BIZ_TYPE_MAP.getOrDefault(skData.getDeviceType(),SkConst.SK_BIZ_TYPE_SOS);
        appealLog.setBizType(bizType);
        appealLog.setRemark(remark);
        kitchenLogService.save(appealLog);
    }

    /**
     * 创建工单
     * @param orderNo
     * @param skData
     * @return
     */
    private Long createWorkOrder(String orderNo,  ConsoleSkRecordsList skData, String operateBy) {
        String woSeq = workOrderHistoryService.WORK_ORDER_NO_PREFIX + SnowflakeUtil.getSnowflakeId();
        WorkOrderHistory workOrderHistory  = new WorkOrderHistory();
        workOrderHistory.setWoSeq(woSeq);
        workOrderHistory.setPkid("");
        workOrderHistory.setSubsCode(skData.getSubsCode());
        workOrderHistory.setOrderNo(orderNo);
        workOrderHistory.setDeviceId(skData.getDeviceId());
        workOrderHistory.setNewDeviceId("");
        workOrderHistory.setFromSystem(0);
        workOrderHistory.setWorkSystem(3);
        workOrderHistory.setOrderType(skData.getAlarmType());
        workOrderHistory.setHandleStatus(0);
        workOrderHistory.setSpId(skData.getSpId());
        workOrderHistory.setOperatorBy(operateBy);
        workOrderHistoryService.save(workOrderHistory);
        return workOrderHistory.getId();
    }

    /**
     * 创建服务订单
     * @param huiShengAddOrderResponse
     * @param userServiceComboVO
     * @param skData
     */
    @Override
    public void createServiceComboOrder(String orderNo, UserServiceComboVO userServiceComboVO, ConsoleSkRecordsList skData, int isAuto) {
        try {
            ServiceComboOrder serviceComboOrder = new ServiceComboOrder();
            if (userServiceComboVO != null) {
                serviceComboOrder.setComboId(userServiceComboVO.getId());
                serviceComboOrder.setComboDetailId(userServiceComboVO.getDetailId());
                serviceComboOrder.setCode(userServiceComboVO.getCode());
                serviceComboOrder.setUserId(userServiceComboVO.getUserId());
                serviceComboOrder.setPhone(userServiceComboVO.getPhone());
            } else {
                serviceComboOrder.setComboId(0);
                serviceComboOrder.setComboDetailId(0);
                serviceComboOrder.setCode(ConsoleSkDeviceTypeEnum.getTypeByCode(skData.getDeviceType()));
                serviceComboOrder.setUserId(Integer.valueOf(skData.getUserId()));
                serviceComboOrder.setPhone(skData.getPhone());
            }
            serviceComboOrder.setAlarmRecordId(skData.getId());
            serviceComboOrder.setDeviceId(skData.getDeviceId());
            serviceComboOrder.setDeviceName(skData.getDeviceName());
            serviceComboOrder.setDeviceType(skData.getDeviceType());
            serviceComboOrder.setAlarmType(skData.getAlarmType());
            serviceComboOrder.setAlarmTime(DateUtils.toDateTime(skData.getAlarmTime()));
            serviceComboOrder.setAlarmEndTime(DateUtils.toDateTime(skData.getAlarmEndTime()));
            serviceComboOrder.setSubsCode(skData.getSubsCode());
            serviceComboOrder.setAlarmCount(skData.getAlarmCount());
            serviceComboOrder.setInstallPosition(skData.getContactAddress());
            serviceComboOrder.setThirdOrderId(orderNo);
            serviceComboOrder.setThirdOrderNo(orderNo);
            serviceComboOrder.setThirdOrderStatus("0");
            serviceComboOrder.setIsAuto(isAuto);
            serviceComboOrder.setSpId(skData.getSpId());
            serviceComboOrderMapper.insert(serviceComboOrder);
        }catch (Exception e){
            log.error("createServiceComboOrder error:", e);
        }
    }

    /**
     * 格式化备注
     * @param skData
     * @return
     */
    private String getRemark(ConsoleSkRecordsList skData) {
        String event;
        if (skData.getDeviceType() == 1) {
            event = "30min按键" + skData.getAlarmCount() + "次";
        } else if (skData.getDeviceType() == 4) {
            event = "防拆报警/密码错误连续5次";
        } else {
            Date start = DateUtil.parse(skData.getAlarmTime(), "yyyy-MM-dd HH:mm:ss");
            Date end = new Date();
            if (!StringUtils.isEmpty(skData.getAlarmEndTime())) {
                end = DateUtil.parse(skData.getAlarmEndTime(), "yyyy-MM-dd HH:mm:ss");
            }
            String durationDate = getDurationDate(start, end);
            event = "报警持续时长：" + durationDate;
        }
        String deviceTypeName = DeviceType.parse(skData.getDeviceType()).getName();
        String remark = deviceTypeName + "：报警开始时间：" + skData.getAlarmTime() + "，" + event;
        if (StringUtils.isEmpty(skData.getBackupPhone())) {
            return remark;
        }
        return remark + "，备用手机号：" + skData.getBackupPhone();
    }

    /**
     * 获取报警时长
     * @param startDate
     * @param endDate
     * @return
     */
    private String getDurationDate(Date startDate, Date endDate) {
        String formatBetween = DateUtil.formatBetween(endDate, startDate, BetweenFormatter.Level.SECOND);
        formatBetween = formatBetween.replace(BetweenFormatter.Level.SECOND.getName(), "");
        if (formatBetween.contains(BetweenFormatter.Level.MINUTE.getName())) {
            formatBetween = formatBetween.replace(BetweenFormatter.Level.MINUTE.getName(), split_m);
        } else {
            formatBetween = "00" + split_m + formatBetween;
        }
        if (formatBetween.contains(BetweenFormatter.Level.HOUR.getName())) {
            formatBetween = formatBetween.replace(BetweenFormatter.Level.HOUR.getName(), split_m);
        } else {
            formatBetween = "00" + split_m + formatBetween;
        }
        if (formatBetween.contains(BetweenFormatter.Level.DAY.getName())) {
            formatBetween = formatBetween.substring(formatBetween.indexOf(BetweenFormatter.Level.DAY.getName()), formatBetween.length());
            formatBetween = "59" + formatBetween.substring(formatBetween.indexOf(split_m));
        }
        StringBuilder format = new StringBuilder();
        String[] split = formatBetween.split(split_m);
        for (String str : split) {
            String s = str + split_m;
            if (s.length() == 2) {
                format.append("0").append(s);
            } else {
                format.append(s);
            }
        }
        if (format.substring(format.length() - 1).contains(split_m)) {
            format = new StringBuilder(format.substring(0, format.length() - 1));
        }
        return format.toString();
    }
}
